home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus Special 23 / AMIGAplus Sonderheft 23 (2000)(Falke)(DE)[!].iso / Updates / Datatypes / JPEG-DT / Source / dispatcher.c < prev    next >
C/C++ Source or Header  |  1999-11-14  |  11KB  |  455 lines

  1. #include <clib/alib_protos.h>
  2. #include <pragma/datatypes_lib.h>
  3. #include <pragma/dos_lib.h>
  4. #include <pragma/exec_lib.h>
  5. #include <pragma/graphics_lib.h>
  6. #include <pragma/intuition_lib.h>
  7. #include <pragma/jpeg_lib.h>
  8. #include <pragma/render_lib.h>
  9. #include <pragma/utility_lib.h>
  10. #include <render/renderhooks.h>
  11. #include <cybergraphx/cybergraphics.h>
  12. #include <datatypes/pictureclass.h>
  13. #include <exec/memory.h>
  14. #include <intuition/icclass.h>
  15. #include <string.h>
  16. #include "class.h"
  17.  
  18. struct Arg1
  19. {
  20. long *mode,*dither,*depth,*dct,*scale,*quality,*smooth,gray,prog;
  21. };
  22.  
  23. ULONG SaveJPEG(IClass *cl,Object *obj,dtWrite *msg);
  24.  
  25. extern Library *SuperClassBase;
  26.  
  27. void ReadPrefs(Data *data)
  28. {
  29. char *var;
  30. data->mode=1;
  31. data->dither=0;
  32. data->depth=8;
  33. data->dct=0;
  34. data->scale=1;
  35. data->quality=75;
  36. data->smooth=0;
  37. data->gray=0;
  38. data->prog=0;
  39. if(var=(char *)AllocVec(512,0))
  40.     {
  41.     if(GetVar("ENV:DataTypes/jpeg.prefs",var,512,LV_VAR|GVF_GLOBAL_ONLY)>=0)
  42.         {
  43.         RDArgs *rdargs;
  44.       if(rdargs=(RDArgs *)AllocDosObject(DOS_RDARGS,0))
  45.             {
  46.             RDArgs *args;
  47.             Arg1 para;
  48.             rdargs->RDA_Source.CS_Buffer=var;
  49.             rdargs->RDA_Source.CS_Length=strlen(var);
  50.             rdargs->RDA_Source.CS_CurChr=0;
  51.             memset(¶,0,sizeof(Arg1));
  52.             if(args=ReadArgs("MODE/A/N,DITHER/A/N,DEPTH/A/N,DCT/A/N,SCALE/A/N,QUALITY/A/N,SMOOTH/A/N,GRAY/S,PROGRESSIVE/S",(long *)¶,rdargs))
  53.                 {
  54.                 data->mode=*para.mode;
  55.                 if(data->mode<0) data->mode=0;
  56.                 else if(data->mode>1) data->mode=1;
  57.                 data->dither=*para.dither;
  58.                 if(data->dither<0) data->dither=0;
  59.                 else if(data->dither>1) data->dither=1;
  60.                 data->depth=*para.depth;
  61.                 if(data->depth<3) data->depth=3;
  62.                 else if(data->depth>8) data->depth=8;
  63.                 data->dct=*para.dct;
  64.                 if(data->dct<0) data->dct=0;
  65.                 else if(data->dct>2) data->dct=2;
  66.                 data->scale=*para.scale;
  67.                 if(data->scale<0) data->scale=0;
  68.                 else if(data->scale>3) data->scale=3;
  69.                 data->scale=1<<data->scale;
  70.                 data->quality=*para.quality;
  71.                 if(data->quality<1) data->quality=1;
  72.                 else if(data->quality>100) data->quality=100;
  73.                 data->smooth=*para.smooth;
  74.                 if(data->smooth<0) data->smooth=0;
  75.                 else if(data->smooth>100) data->smooth=100;
  76.                 data->gray=para.gray;
  77.                 data->prog=para.prog;
  78.                 FreeArgs(args);
  79.                 }
  80.             FreeDosObject(DOS_RDARGS,rdargs);
  81.             }
  82.         }
  83.     FreeVec(var);
  84.     }
  85. if(SuperClassBase->lib_Version<43) data->mode=0;
  86. }
  87.  
  88. struct JPEGINFO
  89. {
  90. Object *obj;
  91. RastPort *rp,*trp;
  92. UBYTE *buffer;
  93. UWORD d,gray;
  94. };
  95.  
  96. static void _getline(UBYTE *scanline,ULONG y,ULONG numb,JPEGINFO *info)
  97. {
  98. if(info->gray) WritePixelLine8(info->rp,0,y,numb,scanline,info->trp);
  99. else
  100.     {
  101.     ULONG w=numb/3;
  102.     if(info->d>8) DoMethod(info->obj,PDTM_WRITEPIXELARRAY,scanline,RECTFMT_RGB,numb,0,y,w,1);
  103.     else
  104.         {
  105.         register ULONG i;
  106.         register UBYTE *p1,*p2;
  107.         p1=info->buffer+w*y*4;
  108.         p2=scanline;
  109.         for(i=0;i<w;i++,p1+=4,p2+=3)
  110.             {
  111.             p1[1]=p2[0];
  112.             p1[2]=p2[1];
  113.             p1[3]=p2[2];
  114.             }
  115.         }
  116.     }
  117. }
  118.  
  119. static ULONG getline(register __a0 UBYTE *scanline,register __d0 ULONG line,register __d1 ULONG numb,register __a1 void *userdata)
  120. {
  121. _getline(scanline,line-1,numb,(JPEGINFO *)userdata);
  122. return 0;
  123. }
  124.  
  125. ULONG Colors2DT(Object *obj,UBYTE *color)
  126. {
  127. UBYTE *cr;
  128. ULONG *cregs,i,num,error=0;
  129. GetDTAttrs(obj,PDTA_NumColors,&num,PDTA_ColorRegisters,&cr,PDTA_CRegs,&cregs,TAG_END);
  130. if(cr&&cregs)
  131.     {
  132.     if(color)
  133.         {
  134.         for(i=0;i<num;i++,cr+=3,cregs+=3,color+=4)
  135.             {
  136.             cr[0]=color[1];
  137.             cr[1]=color[2];
  138.             cr[2]=color[3];
  139.             cregs[0]=cr[0]<<24;
  140.             cregs[1]=cr[1]<<24;
  141.             cregs[2]=cr[2]<<24;
  142.             }
  143.         }
  144.     else
  145.         {
  146.         for(i=0;i<num;i++,cr+=3,cregs+=3)
  147.             {
  148.             cr[0]=i;
  149.             cr[1]=i;
  150.             cr[2]=i;
  151.             cregs[0]=i<<24;
  152.             cregs[1]=cregs[0];
  153.             cregs[2]=cregs[0];
  154.             }
  155.         }
  156.     }
  157. else error=ERROR_NO_FREE_STORE;
  158. return error;
  159. }
  160.  
  161. static void FillBMHD(Object *obj,BitMapHeader *bh,ULONG w,ULONG h,ULONG depth)
  162. {
  163. bh->bmh_Left=0;
  164. bh->bmh_Top=0;
  165. bh->bmh_Width=w;
  166. bh->bmh_Height=h;
  167. bh->bmh_PageWidth=w;
  168. bh->bmh_PageHeight=h;
  169. bh->bmh_Depth=depth;
  170. bh->bmh_Compression=cmpByteRun1;
  171. bh->bmh_XAspect=0;
  172. bh->bmh_YAspect=0;
  173. }
  174.  
  175. static void GetMode(Object *obj,BitMapHeader *bh,Data *data)
  176. {
  177. ULONG mode;
  178. mode=BestModeID(
  179. BIDTAG_NominalWidth,bh->bmh_PageWidth,BIDTAG_NominalHeight,bh->bmh_PageHeight,
  180. BIDTAG_DesiredWidth,bh->bmh_Width,BIDTAG_DesiredHeight,bh->bmh_Height,
  181. BIDTAG_Depth,bh->bmh_Depth,
  182. BIDTAG_DIPFMustNotHave,DIPF_IS_DUALPF|DIPF_IS_PF2PRI|DIPF_IS_HAM|DIPF_IS_EXTRAHALFBRITE,TAG_END);
  183. SetDTAttrs(obj,0,0,PDTA_ModeID,mode,TAG_END);
  184. if(bh->bmh_Depth<=8) SetDTAttrs(obj,0,0,PDTA_NumColors,1<<bh->bmh_Depth,TAG_END);
  185. }
  186.  
  187. static ULONG GetBody_Gray(JPEGDecHandle *jph,BitMapHeader *bh,BitMap *bm,Data *data)
  188. {
  189. ULONG error=0;
  190. UBYTE *buffer;
  191. RastPort rp;
  192. if(buffer=(UBYTE *)AllocBufferFromJPEG(jph,JPG_ScaleDenom,data->scale,TAG_END))
  193.     {
  194.     if(!DecompressJPEG(jph,JPG_DestRGBBuffer,buffer,JPG_ScaleDenom,data->scale,JPG_DCTMethod,data->dct,TAG_END))
  195.         {
  196.         Chunky2BitMap(buffer,0,0,bh->bmh_Width,bh->bmh_Height,bm,0,0,TAG_END);
  197.         }
  198.     else error=ERROR_NO_FREE_STORE;
  199.     FreeJPEGBuffer(buffer);
  200.     }
  201. else
  202.     {
  203.     BitMap *tbm;
  204.     if(tbm=AllocBitMap(bh->bmh_Width,1,8,BMF_MINPLANES,bm))
  205.         {
  206.         RastPort trp;
  207.         InitRastPort(&rp);
  208.         InitRastPort(&trp);
  209.         rp.BitMap=bm;
  210.         trp.BitMap=tbm;
  211.         JPEGINFO info={0,&rp,&trp,0,8,1};
  212.         if(DecompressJPEG(jph,JPG_DecompressHook,getline,JPG_DecompressUserData,&info,JPG_ScaleDenom,data->scale,JPG_DCTMethod,data->dct,TAG_END)) error=ERROR_NO_FREE_STORE;
  213.         FreeBitMap(tbm);
  214.         }
  215.     else error=ERROR_NO_FREE_STORE;
  216.     }
  217. return error;
  218. }
  219.  
  220. static ULONG GetBody_RGB(Object *obj,JPEGDecHandle *jph,BitMapHeader *bh,Data *data)
  221. {
  222. ULONG error=0;
  223. UBYTE *buffer;
  224. if(buffer=(UBYTE *)AllocBufferFromJPEG(jph,JPG_ScaleDenom,data->scale,TAG_END))
  225.     {
  226.     if(!DecompressJPEG(jph,JPG_DestRGBBuffer,buffer,JPG_ScaleDenom,data->scale,JPG_DCTMethod,data->dct,TAG_END))
  227.         {
  228.         DoMethod(obj,PDTM_WRITEPIXELARRAY,buffer,RECTFMT_RGB,bh->bmh_Width*3,0,0,bh->bmh_Width,bh->bmh_Height);
  229.         }
  230.     else error=ERROR_NO_FREE_STORE;
  231.     FreeJPEGBuffer(buffer);
  232.     }
  233. else
  234.     {
  235.     JPEGINFO info={obj,0,0,0,24,0};
  236.     if(DecompressJPEG(jph,JPG_DecompressHook,getline,JPG_DecompressUserData,&info,JPG_ScaleDenom,data->scale,JPG_DCTMethod,data->dct,TAG_END)) error=ERROR_NO_FREE_STORE;
  237.     }
  238. return error;
  239. }
  240.  
  241. static ULONG GetBody_RGB8(Object *obj,JPEGDecHandle *jph,BitMapHeader *bh,BitMap *bm,Data *data)
  242. {
  243. ULONG error=0;
  244. UBYTE *rgb;
  245. if(rgb=(UBYTE *)AllocVec(4*bh->bmh_Width*bh->bmh_Height,MEMF_CLEAR))
  246.     {
  247.     JPEGINFO info={obj,0,0,rgb,bh->bmh_Depth,0};
  248.     if(!DecompressJPEG(jph,
  249.         JPG_DecompressHook,getline,
  250.         JPG_DecompressUserData,&info,
  251.         JPG_ScaleDenom,data->scale,
  252.         JPG_DCTMethod,data->dct,
  253.         TAG_END))
  254.         {
  255.         APTR rmh;
  256.         if(rmh=CreateRMHandler(RND_MemType,RMHTYPE_POOL,TAG_END))
  257.             {
  258.             ULONG *palette;
  259.             if(palette=CreatePalette(RND_RMHandler,rmh,TAG_END))
  260.                 {
  261.                 APTR hst;
  262.                 if(hst=CreateHistogram(RND_RMHandler,rmh,TAG_END))
  263.                     {
  264.                     if(AddRGBImage(hst,(ULONG *)rgb,bh->bmh_Width,bh->bmh_Height,TAG_END)==ADDH_SUCCESS)
  265.                         {
  266.                         ULONG numc;
  267.                         GetDTAttrs(obj,PDTA_NumColors,&numc,TAG_END);
  268.                         if(ExtractPalette(hst,palette,numc,TAG_END)==EXTP_SUCCESS)
  269.                             {
  270.                             UBYTE *chunky;
  271.                             if(chunky=(UBYTE *)AllocVec(bh->bmh_Width*bh->bmh_Height,0))
  272.                                 {
  273.                                 if(Render((ULONG *)rgb,bh->bmh_Width,bh->bmh_Height,chunky,palette,RND_DitherMode,data->dither,TAG_END)==REND_SUCCESS)
  274.                                     {
  275.                                     UBYTE *color;
  276.                                     if(color=(UBYTE *)AllocVec((1<<bh->bmh_Depth)*4,0))
  277.                                         {
  278.                                         ExportPalette(palette,color,TAG_END);
  279.                                         if(!(error=Colors2DT(obj,color))) Chunky2BitMap(chunky,0,0,bh->bmh_Width,bh->bmh_Height,bm,0,0,TAG_END);
  280.                                         FreeVec(color);
  281.                                         }
  282.                                     else error=ERROR_NO_FREE_STORE;
  283.                                     }
  284.                                 else error=ERROR_NO_FREE_STORE;
  285.                                 FreeVec(chunky);
  286.                                 }
  287.                             else error=ERROR_NO_FREE_STORE;
  288.                             }
  289.                         else error=ERROR_NO_FREE_STORE;
  290.                         }
  291.                     else error=ERROR_NO_FREE_STORE;
  292.                     DeleteHistogram(hst);
  293.                     }
  294.                 else error=ERROR_NO_FREE_STORE;
  295.                 DeletePalette(palette);
  296.                 }
  297.             else error=ERROR_NO_FREE_STORE;
  298.             DeleteRMHandler(rmh);
  299.             }
  300.         else error=ERROR_NO_FREE_STORE;
  301.         }
  302.     else error=ERROR_NO_FREE_STORE;
  303.     FreeVec(rgb);
  304.     }
  305. else error=ERROR_NO_FREE_STORE;
  306. return error;
  307. }
  308.  
  309. static ULONG GetPicture(IClass *cl,Object *obj)
  310. {
  311. ULONG error=0;
  312. long err;
  313. BPTR file;
  314. BitMapHeader *bh;
  315. GetDTAttrs(obj